/* 
 * File:   Grid.cpp
 * Author: eliana
 *
 * Created on October 20, 2012, 7:46 PM
 */

#include "Grid.h"

Grid::Grid( std::vector<Object*>& objects )
{
    _cells.clear();
    buildBoundingBox( objects );
}



Grid::~Grid()
{
    for (unsigned int i = 0; i < _cells.size(); i++)
    {
        delete _cells[i];
    }    
    _cells.clear();
}



Box* Grid::getBoundingBox()
{
    return _boundingBox;
}



void Grid::buildBoundingBox( std::vector<Object*>& objects )
{
    Vector4D bbMin, bbMax;
    
    objects[0]->getBoundingBox( bbMin, bbMax );
    
    for (int objID = 1; objID < objects.size(); ++objID)
    {
        Vector4D objMin, objMax;
        objects[objID]->getBoundingBox( objMin, objMax );
        
        bbMin.x = std::min( bbMin.x, objMin.x );
        bbMin.y = std::min( bbMin.y, objMin.y );
        bbMin.z = std::min( bbMin.z, objMin.z );
        
        bbMax.x = std::max( bbMax.x, objMax.x );
        bbMax.y = std::max( bbMax.y, objMax.y );
        bbMax.z = std::max( bbMax.z, objMax.z );
    }
    
    // Adds tolerance to avoid precision problems
    Vector4D gap = bbMax - bbMin;
    gap *= 0.01;
    _boundingBox = new Box( bbMin - gap, bbMax + gap );
}



bool Grid::boxOverlap( Vector4D aMin, Vector4D aMax, Vector4D bMin, Vector4D bMax )
{
    if (aMax.x < bMin.x) return false; // a is left of b
    if (aMin.x > bMax.x) return false; // a is right of b
    if (aMax.y < bMin.y) return false; // a is above b
    if (aMin.y > bMax.y) return false; // a is below b
    if (aMax.z < bMin.z) return false; // a is in front of b
    if (aMin.z > bMax.z) return false; // a is behind b
    
    return true; // boxes overlap
}
